<?php

namespace Sharks\Core\Support\Base;

/**
 * 默认参数工具类
 */
class DefValue {
    /**
     * 默认值可以传入某一标量，也可以传入匿名闭包，如检验值为null，则返回闭包执行结果。
     * 示例：
     *  //可以用作某些属性的第一次初始化
     * if (is_null($a)) {
     *      $b = $a;
     * }
     * else {
     *      $b = 'xxx';
     * }
     *
     * $b = DefValue::isNull($id, 'xxx');
     *
     * @param  [type]  $obj     [description]
     * @param  [type]  $default [description]
     * @return boolean          [description]
     */
    public static function isNull($obj, $default = null) {
        if (is_null($obj)) {
            return self::def($default);
        }
        return $obj;
    }

    /**
     * 如果为空，则返回默认值
     * $a = DefValue::isEmpty($array, array('x', 'y'));
     * $a = DefValue::isEmpty($array, function() {
     *       return 1+1;
     * });
     * @param $obj
     * @param null $default
     * @return mixed
     */
    public static function isEmpty($obj, $default = null) {
        if (empty($obj) || Str::isEmpty($obj)) {
            return self::def($default);
        }
        return $obj;
    }

    /**
     * 返回默认值
     * 如果默认值为标量值，直接返回
     * 如果默认值为闭包，执行后返回
     *
     * @param  mixed|Closure $default 默认值
     * @return mixed         默认值
     */
    public static function def($default) {
        if (!is_null($default) && (is_callable($default))) {
            return $default();
        }
        else {
            return $default;
        }
    }

    /**
     * 从一个映射中抓取指定数据，如果没有对应数据，则返回默认值。
     * $a = array("id"=>1);
     * if (isset($a['name')) {
     *      // do something
     *      $b = $a['name'];
     * }
     * else {
     *      $b = 'xxx';
     * }
     *
     * $b = DefValue::pick($a, 'name', 'xxx');
     *
     * @param  array  $map     [description]
     * @param  [type] $value   [description]
     * @param  [type] $default [description]
     * @return [type]          [description]
     */
    public static function pick(array $map, $value, $default = null) {
        if (empty($map)) {
            return DefValue::def($default);
        }

        if (isset($map[$value])) {
            return $map[$value];
        }
        return DefValue::def($default);
    }
}